package javase.ch02.method;

import java.util.concurrent.TimeUnit;

/**
 * @Desc TODO
 * @Author chenmin
 * @Date 2025/10/30
 *
 * Thread类
 * 1.构造方法
 *   public Thread(Runnable target, String name)
 *
 * 2.静态常量
 * public final static int MIN_PRIORITY = 1;   优先级最小值
 * public final static int NORM_PRIORITY = 5;  默认优先级
 * public final static int MAX_PRIORITY = 10;  优先级最大值
 *
 * 3.常用API方法
 *  public static native void yield();    根据线程的优先级进行退让
 *  属于Thread类的静态方法，一旦调用yield()，当前线程会进行退让，退让给优先级更高的线程；
 *  出现 “假意退让” 的现象，还是会继续参与 “时间片的争抢”，只要再次抢占到时间片就会继续执行任务。
 *
 *  public static native void sleep(long millis) throws InterruptedException;   沉睡
 *  属于Thread类的静态方法，一旦调用sleep()，当前线程会释放CPU执行权（即释放时间片），进入沉睡状态；
 *  此时指定沉睡时间，是它的 “最短不执行任务的时间” ，因为时间结束后，仍然需要争抢时间片，抢到后才能执行任务。
 *
 *  public final synchronized void join(long millis)   计时等待
 *  public final void join()  无限等待
 *
 *  面试题 -  yield() & sleep() & join() 区别
 *  1.yield() & sleep()   属于静态方法，可以直接使用Thread类名调用 ； 而join()是非静态方法，创建Thread线程对象调用；
 *  2.sleep(long millis)  属于计时等待，进入沉睡状态后释放时间片，直到沉睡时间结束，仍然需要继续争抢时间片，抢到后才能继续执行任务；
 *  3.yield()   假意退让给优先级更高的线程，但是又会立马争抢时间片，一旦抢到时间片，会继续执行任务；
 *  4.join(long millis)计时等待 、 join()无限等待
 *  如果使用无限等待，只能等调用者执行结束，才可以继续执行；
 *  如果使用计时等待，等待时间结束，继续争抢时间片，抢到时间片后可以继续执行任务；
 */
public class YieldDemo {

    public static void main(String[] args) {

        new Thread(()->{
            for (int i = 0; i < 5; i++) {
                System.out.println(Thread.currentThread().getName()+" i = "+i);

                //线程沉睡，时间单位是ms毫秒
                try {
                    Thread.sleep(1000);
                    TimeUnit.SECONDS.sleep(1);
                } catch (InterruptedException e) {
                    throw new RuntimeException(e);
                }

                //假意退让
                //Thread.yield();
            }
        } , "线程1").start();   //优先级默认5


        Thread t2 = new Thread(() -> {
            for (int i = 0; i < 5; i++) {
                System.out.println(Thread.currentThread().getName() + " i = " + i);
            }
        }, "线程2");
        //设置最高优先级 10
        t2.setPriority(Thread.MAX_PRIORITY);
        t2.start();

    }

}
